#include "cMenu.h"
#include "D3D Base.h"

extern pEndScene oEndScene;
extern D3DCOLOR dcBorderColor;
extern D3DCOLOR dcBodyColor;
//-----------------------//
// cMenu::DrawTxt
//-----------------------//
void cMenu::DrawTxt(INT X, INT Y, D3DCOLOR Color, ID3DXFont *font, CONST PCHAR Text, DWORD flag ) 
{		
	if( !Text || *Text == '\0' )
		return;

	RECT Pos = { X, Y, X+500, Y+50 };
	font->DrawTextA( NULL, Text, -1, &Pos, flag/* | DT_NOCLIP*/, Color);
}
//-----------------------//
// cMenu::DrawBox
//-----------------------//
VOID WINAPI cMenu::DrawBox(LPDIRECT3DDEVICE9 pDevice, float x, float y, float w, float h, D3DCOLOR Color) 
{
	struct Vert{
		FLOAT x, y, z, t;
		DWORD Color;
	};

	D3DRECT rec;
	Vert V[4];

	V[0].Color = V[1].Color = V[2].Color = V[3].Color = Color;

	V[0].z  = V[1].z = V[2].z  = V[3].z  = 0;
	V[0].t  = V[1].t = V[2].t  = V[3].t  = 0;

	V[0].x = V[1].x = x;
	V[0].y = V[2].y = y + h;
	V[1].y = V[3].y = y;
	V[2].x = V[3].x = x + w;

	pDevice->SetTexture(0, NULL);
	pDevice->SetPixelShader(NULL);
	pDevice->SetRenderState(D3DRS_CLIPPING,FALSE); 
	pDevice->SetFVF(D3DFVF_XYZRHW | D3DFVF_DIFFUSE | D3DFVF_TEX1);
	pDevice->DrawPrimitiveUP( D3DPT_TRIANGLESTRIP, 2, V, sizeof(Vert));
}

//-----------------------//
// cMenu::DrawMenu
//-----------------------//
void cMenu::DrawMenu(LPDIRECT3DDEVICE9 pDevice)
{	
	MENU_HEIGHT = MENU_Y + MENU_TITLEBOX_HEIGHT + (CUR_VISIBLE_ITEMS * ITEM_HEIGH) + (2 * MENU_BORDER_SIZE) + MENU_HEIGHT_OFFSET;
	// title
	this->DrawBox(pDevice, MENU_X+MENU_BORDER_SIZE, MENU_Y+MENU_BORDER_SIZE, MENU_WIDTH - (2 * MENU_BORDER_SIZE), MENU_TITLEBOX_HEIGHT, D3DCOLOR_ARGB(255, 0, 80, 95));
	this->DrawTxt(-1*(162 - (MENU_X + MENU_BORDER_SIZE)), MENU_Y + MENU_BORDER_SIZE, D3DCOLOR_ARGB(255,255,255,0), pFontTitle, "Naidmer's czit", DT_CENTER);
	// check for item changes
	CheckForItems(); 
	//then draw body
	this->DrawBox(pDevice, MENU_X + MENU_BORDER_SIZE, MENU_Y + MENU_TITLEBOX_HEIGHT + (2 * MENU_BORDER_SIZE), MENU_WIDTH - (2 * MENU_BORDER_SIZE), MENU_HEIGHT - (2 * MENU_BORDER_SIZE) - MENU_Y - MENU_TITLEBOX_HEIGHT, dcBodyColor);
	// draw borders
		// title box up border
		this->DrawBox(pDevice, MENU_X + MENU_BORDER_SIZE, MENU_Y, MENU_WIDTH - (2 * MENU_BORDER_SIZE), MENU_BORDER_SIZE, dcBorderColor);
		// body down border
		this->DrawBox(pDevice, MENU_X , MENU_HEIGHT, MENU_WIDTH, MENU_BORDER_SIZE, dcBorderColor);
		// title box left && body left
		this->DrawBox(pDevice, MENU_X, MENU_Y, MENU_BORDER_SIZE, MENU_HEIGHT - MENU_Y, dcBorderColor);
		// title box down && body up
		this->DrawBox(pDevice, MENU_X + MENU_BORDER_SIZE, MENU_Y + MENU_TITLEBOX_HEIGHT + MENU_BORDER_SIZE, MENU_WIDTH - (2 * MENU_BORDER_SIZE), MENU_BORDER_SIZE, dcBorderColor);
		// title box right && body right
		this->DrawBox(pDevice,MENU_X + MENU_WIDTH - MENU_BORDER_SIZE, MENU_Y, MENU_BORDER_SIZE, MENU_HEIGHT - MENU_Y, dcBorderColor);

	// display current opt
	for(int i = 0, y = MENU_TITLEBOX_HEIGHT + MENU_Y + (2 * MENU_BORDER_SIZE) + MENU_TOP_TEXT_ALIGNMENT; i < ACTIVE_ITEMS; i++ )
	{
		if(ITEM[i].IsFolder){
			if(i == CUR_OPT){
				this->DrawTxt(MENU_X + MENU_BORDER_SIZE + MENU_LEFT_TEXT_ALIGNMENT , y, D3DCOLOR_ARGB(255,245,255,0), pFont, ITEM[i].ItemName, DT_LEFT);
				this->DrawTxt((-1) * (346 - (MENU_X + MENU_BORDER_SIZE + MENU_LEFT_TEXT_ALIGNMENT)), y, D3DCOLOR_ARGB(255,245,255,0), pFont, *ITEM[i].ItemNum? "[+]" : "[-]",DT_RIGHT );

				y+= ITEM_HEIGH;
			}

			else{
				this->DrawTxt(MENU_X + MENU_BORDER_SIZE + MENU_LEFT_TEXT_ALIGNMENT, y, ITEM[i].ItemNum? D3DCOLOR_ARGB(255,255,255,255) : D3DCOLOR_ARGB(255,255,0,0), pFont, ITEM[i].ItemName, DT_LEFT);
				this->DrawTxt(-1*(346 - (MENU_X + MENU_BORDER_SIZE + MENU_LEFT_TEXT_ALIGNMENT)), y, *ITEM[i].ItemNum? D3DCOLOR_ARGB(255,127,255,0) : D3DCOLOR_ARGB(255,255,0,0), pFont, *ITEM[i].ItemNum? "[+]" : "[-]", DT_RIGHT );

				y+= ITEM_HEIGH;
			}
		}
		else{
			if(ITEM[i].IsVisible){
					if(i == CUR_OPT){
					this->DrawTxt(MENU_X + MENU_BORDER_SIZE + MENU_LEFT_TEXT_ALIGNMENT + MENU_LEFT_TEXT_IN_FOLDER_ALIGNMENT, y, D3DCOLOR_ARGB(255,245,255,0), pFont, ITEM[i].ItemName, DT_LEFT);
					this->DrawTxt(-1*(346 - (MENU_X + MENU_BORDER_SIZE + MENU_LEFT_TEXT_ALIGNMENT)), y, D3DCOLOR_ARGB(255,245,255,0), pFont,  ITEM[i].opt[ITEM[i].CurOptNum] ,DT_RIGHT );
				
					y+= ITEM_HEIGH;
				}

				else{
					this->DrawTxt(MENU_X + MENU_BORDER_SIZE + MENU_LEFT_TEXT_ALIGNMENT + MENU_LEFT_TEXT_IN_FOLDER_ALIGNMENT, y, ITEM[i].ItemNum? D3DCOLOR_ARGB(255,255,255,255) : D3DCOLOR_ARGB(255,255,0,0), pFont, ITEM[i].ItemName, DT_LEFT);
					this->DrawTxt(-1*(346 - (MENU_X + MENU_BORDER_SIZE + MENU_LEFT_TEXT_ALIGNMENT)), y, *ITEM[i].ItemNum? D3DCOLOR_ARGB(255,127,255,0) : D3DCOLOR_ARGB(255,255,0,0), pFont, ITEM[i].opt[ITEM[i].CurOptNum], DT_RIGHT );

					y+= ITEM_HEIGH;
				}
			}
		}
	}
}
//-----------------------//
// cMenu::cMenu
//-----------------------//
cMenu::cMenu()
{
	CUR_OPT = 0;
	ACTIVE_ITEMS = 0;
	CUR_VISIBLE_ITEMS = 0;

	//--------------------------------//
	MENU_X = 20; //20
	MENU_Y = 25; //25
	MENU_WIDTH = 185;
	MENU_BORDER_SIZE = 5;
	MENU_LEFT_TEXT_ALIGNMENT = 4;
	MENU_LEFT_TEXT_IN_FOLDER_ALIGNMENT = 5;
	MENU_TOP_TEXT_ALIGNMENT = 5;
	MENU_HEIGHT_OFFSET = 10;

	MENU_TITLEBOX_HEIGHT = 20; //25
	//--------------------------------//
}
//-----------------------//
// cMenu::~cMenu
//-----------------------//
cMenu::~cMenu()
{
	for(int i = 0; i < ACTIVE_ITEMS; i++)
	{
		delete[] ITEM[i].ItemName;
	}
	for(int i = 0; i < real_ItemOpt_len; i++)
	{
		for(int j = 0;j < ITEM[i].OptNum; i++){
			delete[] ITEM[i].opt[j];
			delete[] ITEM[i].s_opt;
		}
	}

	pFont->Release();
	pFontTitle->Release();
}
//-----------------------//
// cMenu::AddItem
//-----------------------//
void cMenu::AddItem(char* ItemName, bool IsFolder, short* ItemNum, char* ItemOpt)
{
	//pTools->XorStr(ItemName);

	ITEM[ACTIVE_ITEMS].IsFolder = IsFolder;
	short len = strlen(ItemName);
	ITEM[ACTIVE_ITEMS].ItemName = new char[len+1];
	for(int i = 0; i < len; i++) ITEM[ACTIVE_ITEMS].ItemName[i] = ItemName[i]; 
	ITEM[ACTIVE_ITEMS].ItemName[len] = 0;
	ITEM[ACTIVE_ITEMS].ItemNum = ItemNum;
	ITEM[ACTIVE_ITEMS].IsVisible = true;
	ITEM[ACTIVE_ITEMS].CurOptNum = 0;
	CUR_VISIBLE_ITEMS++;
	if(ItemOpt){
		real_ItemOpt_len = 0;
		ItemOpt_len = strlen(ItemOpt);
		ITEM[ACTIVE_ITEMS].opt = new char*[ItemOpt_len/2];
		ItemOpt_copy = new char[ItemOpt_len +1];
		memcpy(ItemOpt_copy, ItemOpt, ItemOpt_len);
		ItemOpt_copy[ItemOpt_len] = 0;
		char* temp;

		ITEM[ACTIVE_ITEMS].opt[0] = new char[ strlen((temp = strtok(ItemOpt_copy, "|"))) +1];
		ITEM[ACTIVE_ITEMS].s_opt = new string[ItemOpt_len/2];
		ITEM[ACTIVE_ITEMS].s_opt[0].assign (temp);
		ITEM[ACTIVE_ITEMS].opt[0] = (char*)ITEM[ACTIVE_ITEMS].s_opt[0].c_str();
		real_ItemOpt_len++;
		for(int i = 1; ITEM[ACTIVE_ITEMS].opt[i-1] != NULL; i++)
		{
			temp = strtok(NULL, "|");
			
			if(!temp)
				break;

			real_ItemOpt_len++;
			ITEM[ACTIVE_ITEMS].opt[i] = new char[ strlen(temp) +1];
			ITEM[ACTIVE_ITEMS].s_opt[i].assign (temp);
			ITEM[ACTIVE_ITEMS].opt[i] = (char*)ITEM[ACTIVE_ITEMS].s_opt[i].c_str();

		}
		ITEM[ACTIVE_ITEMS].OptNum = real_ItemOpt_len;

		delete[] ItemOpt_copy;
	}
	else{
		ITEM[ACTIVE_ITEMS].opt = new char*[2];
		ITEM[ACTIVE_ITEMS].opt[0] = "Off";
		ITEM[ACTIVE_ITEMS].opt[1] = "On";
		ITEM[ACTIVE_ITEMS].OptNum = 2;
	}

	ACTIVE_ITEMS++; 
}
//-----------------------//
// cMenu::CheckForItems
//-----------------------//
void cMenu::CheckForItems()
{
	static bool bChange = false;

	if( GetAsyncKeyState( VK_LEFT ) &1 ){ 
		if( ITEM[CUR_OPT].IsFolder && *ITEM[CUR_OPT].ItemNum ){
			for(int i = CUR_OPT + 1;; i++){
				if( ITEM[i].IsFolder )
					break;
				if( i == ACTIVE_ITEMS )
					break;

				ITEM[i].IsVisible = true;
				CUR_VISIBLE_ITEMS++;
			}
		}
		*ITEM[CUR_OPT].ItemNum = false;
		ITEM[CUR_OPT].CurOptNum--;
		if( ITEM[CUR_OPT].CurOptNum == -1 )
			ITEM[CUR_OPT].CurOptNum = 0;

		*ITEM[CUR_OPT].ItemNum = ITEM[CUR_OPT].CurOptNum;
	}

	else if( GetAsyncKeyState( VK_RIGHT ) &1 ){ 
		if( ITEM[CUR_OPT].IsFolder && !*ITEM[CUR_OPT].ItemNum ){
			for(int i = CUR_OPT + 1;; i++){
				if( ITEM[i].IsFolder )
					break;
				if( i == ACTIVE_ITEMS ) // ?
					break;
			
				ITEM[i].IsVisible = false;
				CUR_VISIBLE_ITEMS--;
			}
		}
		*ITEM[CUR_OPT].ItemNum = true;
		ITEM[CUR_OPT].CurOptNum++;
		if( ITEM[CUR_OPT].CurOptNum == ITEM[CUR_OPT].OptNum )
			ITEM[CUR_OPT].CurOptNum--;
		*ITEM[CUR_OPT].ItemNum = ITEM[CUR_OPT].CurOptNum;
	}

	else if(GetAsyncKeyState(VK_UP) &1){ 
		CUR_OPT--;
		if(CUR_OPT == -1){
			CUR_OPT = ACTIVE_ITEMS-1;
		}
		if( !ITEM[CUR_OPT].IsVisible ){
			for(int i = CUR_OPT ;; i--){
				if( ITEM[i].IsFolder ){
					CUR_OPT = i;
					break;
				}
				CUR_OPT--;
			}
			bChange = true;
		}
	}

	else if( GetAsyncKeyState(VK_DOWN) &1 ){
		if( ITEM[CUR_OPT].IsFolder && *ITEM[CUR_OPT].ItemNum ){ 
			for(int i = CUR_OPT + 1;; i++){ 
				if( ITEM[i].IsVisible )
					break;
				if( i == ACTIVE_ITEMS )
					break;

				CUR_OPT++;
			}
		}
		
		CUR_OPT++;
		if( CUR_OPT == ACTIVE_ITEMS ){
				CUR_OPT = 0;
		}
	}
}